package com.jerry.lifecyclemonitor;

import java.util.concurrent.Callable;
//将线程执行内容作为执行类封装，同时将线程监听封装到生命周期类中，并封装监听组装范式通过类进行封装。

public class ObservableThread<T> extends Thread implements Observable {

    private Callable<T> callable;

    private TaskLifecycle<T> taskLifecycle;

    private Cycle cycle;

     public ObservableThread(Callable callable,TaskLifecycle taskLifecycle){
         this.callable = callable;
         this.taskLifecycle = taskLifecycle;
     }
    @Override
    public final void run() {
        T result = null;
        updateCycle(Cycle.STARTED, null, null);
        try {
            updateCycle(Cycle.RUNNING, null, null);
            result = callable.call();
            updateCycle(Cycle.DONE, result, null);
        } catch (Exception e) {
            updateCycle(Cycle.ERROR, null, e);
        }
    }

    @Override
    public Cycle getCycle() {
        return null;
    }

    public void interrupt() {

        this.isInterrupted();
    }

    private void updateCycle(Cycle cycle, T result, Exception e) {

        this.cycle = cycle;
        switch (cycle) {
            case STARTED:
                taskLifecycle.onStart(this);
                break;
            case RUNNING:
                taskLifecycle.onRunning(this);
                break;
            case DONE:
                taskLifecycle.onFinish(this, result);
                break;
            case ERROR:
                taskLifecycle.onError(this, e);
                break;
            default:;
        }


    }

    public static void main(String[] args) {
         Callable<String> stringCallable = new Callable<String>() {
             @Override
             public String call() throws Exception {
                 Thread.sleep(10000);
                 throw new RuntimeException("11111");
//                 return "success";
             }
         };
        TaskLifecycle taskLifecycle = new TaskLifecycle.EmptyTaskLifecycle<String>(){
            @Override
            public void onStart(Thread thread) {
                System.out.println("Thread started");
            }

            @Override
            public void onRunning(Thread thread) {
                System.out.println("Thread running");

            }

            @Override
            public void onFinish(Thread thread, String result) {
                System.out.println("Thread finished");

            }

            @Override
            public void onError(Thread thread, Exception e) {
                System.out.println("Thread happends error");
            }

        };
        ObservableThread observableThread = new ObservableThread(stringCallable,taskLifecycle);
        observableThread.start();
    }

}
